Jackson এবং Spring Boot Integration

Java Technologies - জ্যাকসন (Jackson)
374

Jackson হলো Spring Boot-এর ডিফল্ট JSON সিরিয়ালাইজার এবং ডেসিরিয়ালাইজার। Spring Boot-এ Jackson স্বয়ংক্রিয়ভাবে কনফিগার করা থাকে, যা JSON ডেটা প্রসেস করার জন্য ব্যবহার করা হয়। এটি Spring Boot-এর মাধ্যমে সহজেই REST API-তে JSON ডেটা হ্যান্ডল করতে সাহায্য করে।


1. Jackson Integration-এর বৈশিষ্ট্য

  1. ডিফল্ট সিরিয়ালাইজার/ডেসিরিয়ালাইজার: Spring Boot JSON ডেটা প্রসেস করার জন্য Jackson ব্যবহার করে।
  2. অ্যানোটেশন সাপোর্ট: @JsonProperty, @JsonIgnore, @JsonInclude ইত্যাদি Jackson অ্যানোটেশন সরাসরি সমর্থন করে।
  3. Custom Serialization/Deserialization: Spring Boot-এ সহজেই কাস্টম সিরিয়ালাইজার এবং ডেসিরিয়ালাইজার যোগ করা যায়।
  4. Global Configuration: Spring Boot-এর মাধ্যমে Jackson কনফিগারেশনে গ্লোবাল কাস্টমাইজেশন করা যায়।

2. Maven ডিপেন্ডেন্সি

Spring Boot স্টার্টার প্রকল্পে spring-boot-starter-web ডিপেন্ডেন্সি যোগ করলে Jackson স্বয়ংক্রিয়ভাবে অন্তর্ভুক্ত হয়।

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>

3. উদাহরণ: JSON সিরিয়ালাইজেশন এবং ডেসিরিয়ালাইজেশন

মডেল ক্লাস:

import com.fasterxml.jackson.annotation.JsonInclude;

@JsonInclude(JsonInclude.Include.NON_NULL)
public class User {
    private int id;
    private String name;
    private String email;

    // Getters and Setters
    public int getId() {
        return id;
    }

    public void setId(int id) {
        this.id = id;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public String getEmail() {
        return email;
    }

    public void setEmail(String email) {
        this.email = email;
    }
}

Controller:

import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;

@RestController
@RequestMapping("/users")
public class UserController {

    @GetMapping("/{id}")
    public ResponseEntity<User> getUser(@PathVariable int id) {
        User user = new User();
        user.setId(id);
        user.setName("John Doe");
        user.setEmail("john.doe@example.com");
        return ResponseEntity.ok(user);
    }

    @PostMapping
    public ResponseEntity<String> createUser(@RequestBody User user) {
        return ResponseEntity.ok("User created: " + user.getName());
    }
}

API কল এবং JSON আউটপুট:

GET Request:

GET /users/1

Response:

{
  "id": 1,
  "name": "John Doe",
  "email": "john.doe@example.com"
}

POST Request:

POST /users
Content-Type: application/json

{
  "id": 2,
  "name": "Jane Doe",
  "email": "jane.doe@example.com"
}

Response:

User created: Jane Doe

4. Jackson Configuration কাস্টমাইজ করা

Application.properties:

spring.jackson.default-property-inclusion=non_null
spring.jackson.date-format=yyyy-MM-dd

Global Jackson Configuration Bean:

import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.SerializationFeature;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class JacksonConfig {

    @Bean
    public ObjectMapper objectMapper() {
        ObjectMapper objectMapper = new ObjectMapper();
        objectMapper.enable(SerializationFeature.INDENT_OUTPUT); // Pretty Print JSON
        return objectMapper;
    }
}

5. Custom Serializer এবং Deserializer

Custom Serializer:

import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.databind.JsonSerializer;
import com.fasterxml.jackson.databind.SerializerProvider;
import java.io.IOException;

public class CustomUserSerializer extends JsonSerializer<User> {
    @Override
    public void serialize(User user, JsonGenerator gen, SerializerProvider serializers) throws IOException {
        gen.writeStartObject();
        gen.writeNumberField("userId", user.getId());
        gen.writeStringField("userName", user.getName());
        gen.writeEndObject();
    }
}

Serializer ব্যবহার:

import com.fasterxml.jackson.databind.annotation.JsonSerialize;

@JsonSerialize(using = CustomUserSerializer.class)
public class User {
    private int id;
    private String name;
    private String email;

    // Getters and Setters
}

Response:

{
  "userId": 1,
  "userName": "John Doe"
}

6. Spring Boot এবং Jackson এর সুবিধা

  1. ডিফল্ট কনফিগারেশন: Spring Boot-এ Jackson ডিফল্টভাবে অন্তর্ভুক্ত থাকে এবং সাধারণ কাজের জন্য কনফিগারেশনের প্রয়োজন হয় না।
  2. Custom Serialization: কাস্টম সিরিয়ালাইজার এবং ডেসিরিয়ালাইজার সহজেই ইন্টিগ্রেট করা যায়।
  3. Global Settings: Global ObjectMapper ব্যবহার করে কনফিগারেশন প্রয়োগ করা যায়।
  4. RESTful API: REST API ডেভেলপমেন্টের জন্য Jackson অ্যানোটেশনগুলো খুব কার্যকর।

7. Spring Boot Test সহ JSON Validation

JUnit Test:

import com.fasterxml.jackson.databind.ObjectMapper;
import org.junit.jupiter.api.Test;

import static org.assertj.core.api.Assertions.assertThat;

public class UserSerializationTest {

    @Test
    public void testUserSerialization() throws Exception {
        User user = new User();
        user.setId(1);
        user.setName("John Doe");
        user.setEmail("john.doe@example.com");

        ObjectMapper objectMapper = new ObjectMapper();
        String json = objectMapper.writeValueAsString(user);

        assertThat(json).contains("\"id\":1");
        assertThat(json).contains("\"name\":\"John Doe\"");
        assertThat(json).contains("\"email\":\"john.doe@example.com\"");
    }
}

  1. Spring Boot এবং Jackson Integration JSON ডেটা সিরিয়ালাইজ এবং ডেসিরিয়ালাইজ করার জন্য ডিফল্ট সমাধান।
  2. Jackson-এর কাস্টমাইজেশন: Spring Boot-এর মাধ্যমে সহজেই গ্লোবাল বা লোকাল কাস্টমাইজেশন করা যায়।
  3. RESTful API উন্নয়ন: JSON ফরম্যাটে ডেটা বিনিময়ের জন্য Jackson একটি আদর্শ সরঞ্জাম।
  4. Custom Serializer এবং Deserializer: কাস্টম লজিক প্রয়োগের জন্য Jackson খুবই কার্যকর।

Spring Boot এবং Jackson-এর ইন্টিগ্রেশন JSON ডেটা প্রসেসিং সহজ, দ্রুত এবং কার্যকর করে।

Content added By

Spring Boot এর সাথে Jackson ব্যবহার করা

197

Jackson হলো Spring Boot-এ ডিফল্ট JSON সিরিয়ালাইজেশন এবং ডেসিরিয়ালাইজেশন লাইব্রেরি। এটি Spring Boot-এর মাধ্যমে JSON ডেটা প্রক্রিয়াকরণ সহজ করে। Spring Boot অটোমেটিকভাবে Jackson-কে কনফিগার করে RESTful API-তে ইনপুট এবং আউটপুট JSON ডেটার জন্য।


Spring Boot এবং Jackson Integration কেন গুরুত্বপূর্ণ?

  1. JSON হ্যান্ডলিং সহজ করা: Spring Boot-এর মাধ্যমে Jackson স্বয়ংক্রিয়ভাবে ইনপুট (JSON থেকে Java) এবং আউটপুট (Java থেকে JSON) পরিচালনা করে।
  2. Custom Serialization/Deserialization: JSON ডেটা কাস্টমাইজ করার জন্য সহজ ইন্টিগ্রেশন।
  3. Configuration Automation: Spring Boot অটোমেটিক Jackson কনফিগারেশন সরবরাহ করে।
  4. REST API Development: JSON হলো RESTful API-এর প্রধান ডেটা ফরম্যাট, যা Jackson সহজ করে।
  5. ডেটা ভ্যালিডেশন: Spring Boot Bean Validation এবং Jackson একত্রে JSON ডেটার যাচাই নিশ্চিত করে।

Spring Boot-এ Jackson ব্যবহার করার ধাপসমূহ

১. Maven ডিপেন্ডেন্সি (অত্যাবশ্যক নয়)

Spring Boot Starter Web ডিপেন্ডেন্সি ব্যবহার করলে Jackson ডিফল্টভাবে অন্তর্ভুক্ত থাকে। তবুও, যদি প্রয়োজন হয়, নিম্নলিখিত ডিপেন্ডেন্সি যুক্ত করুন:

<dependency>
    <groupId>com.fasterxml.jackson.core</groupId>
    <artifactId>jackson-databind</artifactId>
    <version>2.15.0</version>
</dependency>

২. REST Controller তৈরি করুন

import org.springframework.web.bind.annotation.*;

@RestController
@RequestMapping("/api/users")
public class UserController {

    @PostMapping
    public User createUser(@RequestBody User user) {
        // JSON থেকে Java Object (Deserialization)
        System.out.println("Received User: " + user.getName() + ", Age: " + user.getAge());
        return user; // Java Object থেকে JSON (Serialization)
    }
}

৩. Model Class তৈরি করুন

import com.fasterxml.jackson.annotation.JsonProperty;

public class User {

    @JsonProperty("user_name") // JSON ফিল্ডের নাম কাস্টমাইজ করা
    private String name;

    private int age;

    // Getters এবং Setters
    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }
}

৪. Request এবং Response JSON উদাহরণ

Request JSON:
{
  "user_name": "John Doe",
  "age": 25
}
Response JSON:
{
  "user_name": "John Doe",
  "age": 25
}

Spring Boot-এ Custom Serialization এবং Deserialization

Custom Serializer

import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.databind.JsonSerializer;
import com.fasterxml.jackson.databind.SerializerProvider;
import java.io.IOException;

public class CustomUserSerializer extends JsonSerializer<User> {

    @Override
    public void serialize(User user, JsonGenerator gen, SerializerProvider serializers) throws IOException {
        gen.writeStartObject();
        gen.writeStringField("name", user.getName().toUpperCase());
        gen.writeNumberField("age", user.getAge());
        gen.writeEndObject();
    }
}

Custom Deserializer

import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.databind.DeserializationContext;
import com.fasterxml.jackson.databind.JsonDeserializer;
import java.io.IOException;

public class CustomUserDeserializer extends JsonDeserializer<User> {

    @Override
    public User deserialize(JsonParser p, DeserializationContext ctxt) throws IOException {
        User user = new User();
        user.setName(p.readValueAsTree().get("name").asText().toLowerCase());
        user.setAge(p.readValueAsTree().get("age").asInt());
        return user;
    }
}

ObjectMapper Configuration

import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.module.SimpleModule;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class JacksonConfig {

    @Bean
    public ObjectMapper objectMapper() {
        ObjectMapper objectMapper = new ObjectMapper();
        SimpleModule module = new SimpleModule();
        module.addSerializer(User.class, new CustomUserSerializer());
        module.addDeserializer(User.class, new CustomUserDeserializer());
        objectMapper.registerModule(module);
        return objectMapper;
    }
}

Spring Boot-এ Common Jackson Annotations

  1. @JsonProperty: ফিল্ডের JSON নাম কাস্টমাইজ করতে।
  2. @JsonIgnore: একটি ফিল্ড JSON সিরিয়ালাইজেশনে অন্তর্ভুক্ত না করতে।
  3. @JsonInclude: শর্তসাপেক্ষে ফিল্ড অন্তর্ভুক্ত করতে।

    @JsonInclude(JsonInclude.Include.NON_NULL)
    private String address;
    
  4. @JsonFormat: ডেটা ফরম্যাট কাস্টমাইজ করতে (যেমন, তারিখ)।

    @JsonFormat(pattern = "yyyy-MM-dd")
    private LocalDate birthDate;
    
  5. @JsonCreator এবং @JsonValue: Custom deserialization এবং serialization এর জন্য।

Spring Boot এবং Jackson Integration এর উপকারিতা

  1. সহজ JSON হ্যান্ডলিং: ইনপুট এবং আউটপুট JSON স্বয়ংক্রিয়ভাবে প্রক্রিয়াকরণ।
  2. ডেটা কাস্টমাইজেশন: Custom Serializer এবং Deserializer দিয়ে JSON ডেটা কাস্টমাইজ করা যায়।
  3. অ্যানোটেশন সাপোর্ট: Bean Validation এবং Jackson এর অ্যানোটেশন ব্যবহার করে ডেটা যাচাই এবং প্রক্রিয়াকরণ।
  4. RESTful API ডেভেলপমেন্ট: Spring Boot-এর মাধ্যমে RESTful API ডেভেলপমেন্ট আরো সহজ হয়।
  5. ডেটা ভ্যালিডেশন: JSON ইনপুট ভ্যালিডেশন নিশ্চিত করতে Bean Validation এর সাথে Integration।

Spring Boot-এর সাথে Jackson একটি শক্তিশালী এবং কার্যকর সমাধান যা JSON সিরিয়ালাইজেশন এবং ডেসিরিয়ালাইজেশন প্রক্রিয়া সহজ করে। এটি RESTful API ডেভেলপমেন্টে অত্যন্ত উপযোগী এবং ডেটা ইন্টিগ্রিটি ও নিরাপত্তা নিশ্চিত করতে বিশেষ ভূমিকা পালন করে।

Content added By

Spring এর @RestController এবং @RequestBody এর সাথে Jackson Integration

222

Spring Framework এবং Jackson লাইব্রেরি একত্রে কাজ করে JSON Serialization (Java Object থেকে JSON এ রূপান্তর) এবং Deserialization (JSON থেকে Java Object এ রূপান্তর) সহজ করতে। Spring এর @RestController এবং @RequestBody অ্যানোটেশন ব্যবহার করে Jackson স্বয়ংক্রিয়ভাবে JSON ডেটা এবং Java Object এর মধ্যে ম্যাপিং পরিচালনা করে।


Spring এবং Jackson Integration এর প্রধান বৈশিষ্ট্য

  1. @RequestBody: ইনকামিং JSON ডেটা Java Object এ রূপান্তর করে।
  2. @ResponseBody: Java Object কে JSON আউটপুটে রূপান্তর করে।
  3. Spring Boot এ Jackson ডিফল্টভাবে অন্তর্ভুক্ত থাকে।
  4. Custom Serialization/Deserialization সমর্থন।

প্রয়োজনীয় সেটআপ

Maven ডিপেনডেন্সি (Spring Boot এর জন্য):

Spring Boot Jackson ডিফল্টভাবে অন্তর্ভুক্ত করে। যদি আলাদাভাবে যোগ করতে হয়:

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
    <groupId>com.fasterxml.jackson.core</groupId>
    <artifactId>jackson-databind</artifactId>
    <version>2.15.2</version> <!-- সর্বশেষ ভার্সন -->
</dependency>

Step-by-Step উদাহরণ

১. একটি মডেল ক্লাস তৈরি করা

public class User {
    private String name;
    private int age;
    private String email;

    // Getters and Setters
    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public String getEmail() {
        return email;
    }

    public void setEmail(String email) {
        this.email = email;
    }
}

২. একটি @RestController তৈরি করা

import org.springframework.web.bind.annotation.*;

@RestController
@RequestMapping("/api/users")
public class UserController {

    @PostMapping
    public String createUser(@RequestBody User user) {
        // JSON থেকে User object তৈরি হয়েছে
        return "User created: " + user.getName() + ", Age: " + user.getAge();
    }

    @GetMapping
    public User getUser() {
        // JSON আউটপুটে User object রিটার্ন হবে
        User user = new User();
        user.setName("Alice");
        user.setAge(25);
        user.setEmail("alice@example.com");
        return user;
    }
}

৩. API টেস্ট করা

POST API Call:
  • Request:

    {
      "name": "Bob",
      "age": 30,
      "email": "bob@example.com"
    }
    
  • Response:

    User created: Bob, Age: 30
    
GET API Call:
  • Response:

    {
      "name": "Alice",
      "age": 25,
      "email": "alice@example.com"
    }
    

Custom Serialization/Deserialization

Custom Serializer তৈরি করা

import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.databind.SerializerProvider;
import com.fasterxml.jackson.databind.ser.std.StdSerializer;

import java.io.IOException;

public class UserSerializer extends StdSerializer<User> {

    public UserSerializer() {
        this(null);
    }

    public UserSerializer(Class<User> t) {
        super(t);
    }

    @Override
    public void serialize(User user, JsonGenerator gen, SerializerProvider provider) throws IOException {
        gen.writeStartObject();
        gen.writeStringField("fullName", user.getName());
        gen.writeNumberField("userAge", user.getAge());
        gen.writeEndObject();
    }
}

Custom Serializer সংযুক্ত করা

import com.fasterxml.jackson.databind.annotation.JsonSerialize;

@JsonSerialize(using = UserSerializer.class)
public class User {
    private String name;
    private int age;
    private String email;

    // Getters and Setters
}

Custom Serialization Output:

  • GET API Call:
{
  "fullName": "Alice",
  "userAge": 25
}

Custom Deserializer তৈরি করা

import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.databind.DeserializationContext;
import com.fasterxml.jackson.databind.JsonDeserializer;

import java.io.IOException;

public class UserDeserializer extends JsonDeserializer<User> {

    @Override
    public User deserialize(JsonParser p, DeserializationContext ctxt) throws IOException {
        // JSON Parsing Logic
        return null; // Custom deserialization logic
    }
}

Spring Boot Configuration (Custom ObjectMapper)

Spring Boot এ একটি কাস্টম ObjectMapper সংজ্ঞায়িত করে কাস্টম Serialization/Deserialization সমর্থন যোগ করা যায়।

import com.fasterxml.jackson.databind.ObjectMapper;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class JacksonConfig {

    @Bean
    public ObjectMapper objectMapper() {
        ObjectMapper mapper = new ObjectMapper();
        // Custom configurations
        return mapper;
    }
}

Error Handling (Validation Integration)

Validation এবং Exception Handling:

import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.MethodArgumentNotValidException;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.RestControllerAdvice;

import java.util.HashMap;
import java.util.Map;

@RestControllerAdvice
public class ValidationExceptionHandler {

    @ExceptionHandler(MethodArgumentNotValidException.class)
    public ResponseEntity<Map<String, String>> handleValidationExceptions(MethodArgumentNotValidException ex) {
        Map<String, String> errors = new HashMap<>();
        ex.getBindingResult().getFieldErrors().forEach(error -> {
            errors.put(error.getField(), error.getDefaultMessage());
        });
        return new ResponseEntity<>(errors, HttpStatus.BAD_REQUEST);
    }
}

  1. Spring এর @RestController এবং @RequestBody Jackson এর মাধ্যমে JSON ডেটা হ্যান্ডলিংকে সহজ করে।
  2. Custom Serializer/Deserializer ব্যবহার করে JSON ফরম্যাট সম্পূর্ণ নিয়ন্ত্রণ করা যায়।
  3. Spring Boot এ ডিফল্ট ObjectMapper কাস্টমাইজ করা যায়।
  4. Validation এবং Exception Handling REST API এর জন্য Jackson Integration আরও শক্তিশালী করে।
Content added By

Global ObjectMapper কনফিগারেশন

171

Jackson-এ ObjectMapper JSON serialization এবং deserialization-এর প্রধান ইঞ্জিন। যখন অ্যাপ্লিকেশনে বারবার ObjectMapper ব্যবহার করতে হয়, তখন একটি Global ObjectMapper তৈরি করা এবং সেটিকে কনফিগার করা সবচেয়ে ভালো পদ্ধতি। এটি কোড পুনরাবৃত্তি কমায় এবং কনসিস্টেন্ট JSON প্রসেসিং নিশ্চিত করে।


Global ObjectMapper কী?

Global ObjectMapper হলো একটি একক ObjectMapper ইনস্ট্যান্স যা অ্যাপ্লিকেশনের বিভিন্ন জায়গায় পুনঃব্যবহার করা যায়। এটি সাধারণত কাস্টম কনফিগারেশন দিয়ে সেটআপ করা হয়।

উদাহরণ: ObjectMapper Default Initialization

ObjectMapper objectMapper = new ObjectMapper();

1. Global ObjectMapper কনফিগারেশন পদ্ধতি

কাস্টম ObjectMapper সেটআপ:

import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.SerializationFeature;

public class GlobalObjectMapper {

    private static final ObjectMapper objectMapper = new ObjectMapper();

    static {
        // Include only non-null fields
        objectMapper.setSerializationInclusion(JsonInclude.Include.NON_NULL);

        // Pretty print JSON output
        objectMapper.enable(SerializationFeature.INDENT_OUTPUT);

        // Write dates as ISO-8601 strings
        objectMapper.disable(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS);
    }

    public static ObjectMapper getInstance() {
        return objectMapper;
    }
}

ব্যবহার:

public class Main {
    public static void main(String[] args) throws Exception {
        ObjectMapper objectMapper = GlobalObjectMapper.getInstance();

        // Example JSON serialization
        User user = new User();
        user.id = 101;
        user.name = "John Doe";

        String jsonOutput = objectMapper.writeValueAsString(user);
        System.out.println(jsonOutput);
    }
}

class User {
    public int id;
    public String name;
    public String email; // Will be excluded if null
}

আউটপুট:

{
  "id": 101,
  "name": "John Doe"
}

2. Spring Boot-এ Global ObjectMapper কনফিগারেশন

Spring Boot অ্যাপ্লিকেশন সাধারণত Jackson ObjectMapper কে স্বয়ংক্রিয়ভাবে সরবরাহ করে। আমরা কাস্টম ObjectMapper কনফিগার করতে চাইলে Spring Boot এর @Bean এবং Jackson2ObjectMapperBuilder ব্যবহার করতে পারি।

কাস্টম ObjectMapper Bean:

import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.SerializationFeature;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
public class JacksonConfig {

    @Bean
    public ObjectMapper objectMapper() {
        ObjectMapper mapper = new ObjectMapper();

        // Include non-null fields only
        mapper.setSerializationInclusion(JsonInclude.Include.NON_NULL);

        // Pretty print
        mapper.enable(SerializationFeature.INDENT_OUTPUT);

        // Disable timestamps for dates
        mapper.disable(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS);

        return mapper;
    }
}

ব্যবহার:

@RestController
@RequestMapping("/api")
public class UserController {

    private final ObjectMapper objectMapper;

    public UserController(ObjectMapper objectMapper) {
        this.objectMapper = objectMapper;
    }

    @GetMapping("/user")
    public String getUser() throws Exception {
        User user = new User();
        user.id = 101;
        user.name = "John Doe";

        return objectMapper.writeValueAsString(user);
    }
}

class User {
    public int id;
    public String name;
    public String email; // Will be excluded if null
}

3. ObjectMapper Global Settings

সাধারণ কনফিগারেশন অপশন:

  1. Serialization Features:
    • SerializationFeature.INDENT_OUTPUT: JSON ডেটা ফরম্যাট করা (pretty print)।
    • SerializationFeature.WRITE_DATES_AS_TIMESTAMPS: তারিখ ISO-8601 ফরম্যাটে লেখার জন্য।
  2. Deserialization Features:
    • DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES: অজানা ফিল্ড থাকলে ত্রুটি এড়াতে এটি নিষ্ক্রিয় করা যেতে পারে।

      objectMapper.disable(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES);
      
  3. Inclusion Rules:
    • JsonInclude.Include.NON_NULL: null ফিল্ড JSON-এ এড়িয়ে যাওয়া।
    • JsonInclude.Include.NON_EMPTY: null এবং খালি ফিল্ড বাদ দেওয়া।
  4. Date/Time Handling:
    • ISO-8601 ফরম্যাট:

      objectMapper.disable(SerializationFeature.WRITE_DATES_AS_TIMESTAMPS);
      
  5. Custom Modules:
    • Jackson মডিউল যোগ করার জন্য:

      objectMapper.registerModule(new JavaTimeModule());
      

4. ObjectMapper with Custom Serializer/Deserializer

Custom Serializer:

import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.databind.JsonSerializer;
import com.fasterxml.jackson.databind.SerializerProvider;

import java.io.IOException;

public class CustomNameSerializer extends JsonSerializer<String> {
    @Override
    public void serialize(String value, JsonGenerator gen, SerializerProvider serializers) throws IOException {
        gen.writeString("Name: " + value);
    }
}

Custom Deserializer:

import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.databind.DeserializationContext;
import com.fasterxml.jackson.databind.JsonDeserializer;

import java.io.IOException;

public class CustomNameDeserializer extends JsonDeserializer<String> {
    @Override
    public String deserialize(JsonParser p, DeserializationContext ctxt) throws IOException {
        String name = p.getText();
        return name.replace("Name: ", "");
    }
}

ব্যবহার:

import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;

class User {
    @JsonSerialize(using = CustomNameSerializer.class)
    @JsonDeserialize(using = CustomNameDeserializer.class)
    public String name;
}

5. Testing ObjectMapper Configuration

JUnit টেস্ট দিয়ে কনফিগারেশন পরীক্ষা করা যেতে পারে।

import com.fasterxml.jackson.databind.ObjectMapper;
import org.junit.jupiter.api.Test;

import static org.junit.jupiter.api.Assertions.*;

class ObjectMapperTest {

    @Test
    void testObjectMapperConfiguration() throws Exception {
        ObjectMapper objectMapper = GlobalObjectMapper.getInstance();

        User user = new User();
        user.id = 101;
        user.name = "John Doe";

        String json = objectMapper.writeValueAsString(user);

        assertTrue(json.contains("John Doe"));
        assertFalse(json.contains("null"));
    }
}

উপকারিতা:

  1. Consistency: পুরো অ্যাপ্লিকেশনে একক ObjectMapper ইনস্ট্যান্স ব্যবহার করা।
  2. Reusability: কনফিগারেশন একবার সেটআপ করে সর্বত্র পুনর্ব্যবহার।
  3. Customization: বিভিন্ন serialization/deserialization প্রয়োজন অনুযায়ী কাস্টমাইজেশন।

Jackson-এর Global ObjectMapper কনফিগারেশন API ডেভেলপমেন্ট এবং ডেটা প্রসেসিং আরও সহজ এবং কার্যকর করে তোলে।

Content added By

Spring Boot এবং Jackson এর মাধ্যমে API Development

206

Spring Boot এবং Jackson একত্রে ব্যবহার করে RESTful API তৈরি করা অত্যন্ত সহজ এবং কার্যকর। Spring Boot ডিফল্টভাবে Jackson-কে JSON serialization এবং deserialization-এর জন্য ব্যবহার করে। নিচে Spring Boot এবং Jackson ব্যবহার করে API ডেভেলপমেন্টের ধাপগুলো আলোচনা করা হলো।


Spring Boot এবং Jackson: ইন্টিগ্রেশন ও ডিপেনডেন্সি

Spring Boot ডিফল্টভাবে Jackson-এর উপর নির্ভর করে JSON ডেটা প্রসেসিং পরিচালনা করে। Maven ব্যবহার করলে, নিচের ডিপেনডেন্সি যুক্ত করুন:

Maven ডিপেনডেন্সি:

<dependencies>
    <!-- Spring Boot Starter Web -->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>

    <!-- Spring Boot Starter Validation -->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-validation</artifactId>
    </dependency>
</dependencies>

Step 1: একটি Simple REST Controller তৈরি করুন

1. ডেটা মডেল তৈরি করুন

import jakarta.validation.constraints.NotNull;
import jakarta.validation.constraints.Size;

public class Product {
    private int id;

    @NotNull(message = "Name cannot be null")
    @Size(min = 2, max = 100, message = "Name must be between 2 and 100 characters")
    private String name;

    @NotNull(message = "Price cannot be null")
    private Double price;

    // Getters and Setters
    public int getId() { return id; }
    public void setId(int id) { this.id = id; }

    public String getName() { return name; }
    public void setName(String name) { this.name = name; }

    public Double getPrice() { return price; }
    public void setPrice(Double price) { this.price = price; }
}

2. REST Controller তৈরি করুন

import org.springframework.http.ResponseEntity;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;

import java.util.ArrayList;
import java.util.List;

@RestController
@RequestMapping("/api/products")
public class ProductController {

    private final List<Product> products = new ArrayList<>();

    // Get All Products
    @GetMapping
    public ResponseEntity<List<Product>> getAllProducts() {
        return ResponseEntity.ok(products);
    }

    // Add a New Product
    @PostMapping
    public ResponseEntity<Product> addProduct(@Validated @RequestBody Product product) {
        product.setId(products.size() + 1);
        products.add(product);
        return ResponseEntity.ok(product);
    }

    // Get Product by ID
    @GetMapping("/{id}")
    public ResponseEntity<Product> getProductById(@PathVariable int id) {
        return products.stream()
                .filter(product -> product.getId() == id)
                .findFirst()
                .map(ResponseEntity::ok)
                .orElse(ResponseEntity.notFound().build());
    }
}

Step 2: JSON Serialization এবং Deserialization

Spring Boot ডিফল্টভাবে Jackson ব্যবহার করে @RequestBody এবং @ResponseBody এর মাধ্যমে JSON ডেটা serialize এবং deserialize করে।


Step 3: Advanced Jackson Customization

1. @JsonProperty ব্যবহার করে কাস্টম ফিল্ড নাম

import com.fasterxml.jackson.annotation.JsonProperty;

public class Product {
    private int id;

    @JsonProperty("product_name")
    private String name;

    private Double price;

    // Getters and Setters
    public int getId() { return id; }
    public void setId(int id) { this.id = id; }

    public String getName() { return name; }
    public void setName(String name) { this.name = name; }

    public Double getPrice() { return price; }
    public void setPrice(Double price) { this.price = price; }
}

2. @JsonIgnore দিয়ে ফিল্ড বাদ দেওয়া

import com.fasterxml.jackson.annotation.JsonIgnore;

public class Product {
    private int id;
    private String name;

    @JsonIgnore
    private Double price;

    // Getters and Setters
}

3. Custom Serializer/Deserializer

import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.databind.JsonSerializer;
import com.fasterxml.jackson.databind.SerializerProvider;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;

import java.io.IOException;

public class Product {
    private int id;
    private String name;

    @JsonSerialize(using = CustomPriceSerializer.class)
    private Double price;

    // Getters and Setters
}

class CustomPriceSerializer extends JsonSerializer<Double> {
    @Override
    public void serialize(Double value, JsonGenerator gen, SerializerProvider serializers) throws IOException {
        gen.writeString("$" + value);
    }
}

Step 4: Validation এবং Error Handling

1. Custom Error Message

Spring Boot স্বয়ংক্রিয়ভাবে validation error message প্রদান করে।

উদাহরণ:

@PostMapping
public ResponseEntity<Product> addProduct(@Validated @RequestBody Product product) {
    product.setId(products.size() + 1);
    products.add(product);
    return ResponseEntity.ok(product);
}

2. Global Exception Handling

import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.MethodArgumentNotValidException;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.RestControllerAdvice;

import java.util.HashMap;
import java.util.Map;

@RestControllerAdvice
public class GlobalExceptionHandler {

    @ExceptionHandler(MethodArgumentNotValidException.class)
    public ResponseEntity<Map<String, String>> handleValidationExceptions(MethodArgumentNotValidException ex) {
        Map<String, String> errors = new HashMap<>();
        ex.getBindingResult().getFieldErrors().forEach(error -> 
            errors.put(error.getField(), error.getDefaultMessage())
        );
        return new ResponseEntity<>(errors, HttpStatus.BAD_REQUEST);
    }
}

আউটপুট (Validation Error):

{
  "name": "Name must be between 2 and 100 characters",
  "price": "Price cannot be null"
}

Step 5: Nested Objects এবং Complex JSON Handling

Nested Object মডেল:

public class Order {
    private int orderId;

    @Validated
    private Product product;

    // Getters and Setters
}

Controller Method:

@PostMapping("/orders")
public ResponseEntity<Order> createOrder(@Validated @RequestBody Order order) {
    order.setOrderId(1001);
    return ResponseEntity.ok(order);
}

Spring Boot এবং Jackson-এর মাধ্যমে RESTful API ডেভেলপমেন্ট:

  1. Basic Features: JSON serialization/deserialization সহজে করা যায়।
  2. Advanced Customization: Custom annotations (@JsonProperty, @JsonIgnore, @JsonSerialize) ব্যবহার করে।
  3. Validation and Error Handling: @Validated এবং Global Exception Handler ব্যবহার করে ডেটা integrity নিশ্চিত করা যায়।
  4. Nested Objects: Nested JSON ডেটা সহজেই হ্যান্ডল করা যায়।

Spring Boot এবং Jackson একত্রে ব্যবহার করলে API ডেভেলপমেন্ট দ্রুত, সহজ, এবং কার্যকর হয়।

Content added By
Promotion
NEW SATT AI এখন আপনাকে সাহায্য করতে পারে।

Are you sure to start over?

Loading...